package com.streambolics.data;

import java.util.UUID;
import java.util.logging.Logger;

import javax.jdo.PersistenceManager;
import javax.jdo.annotations.IdentityType;
import javax.jdo.annotations.Inheritance;
import javax.jdo.annotations.InheritanceStrategy;
import javax.jdo.annotations.PersistenceCapable;
import javax.jdo.annotations.Persistent;

import com.streambolics.std.StringExtensions;

@PersistenceCapable(identityType = IdentityType.APPLICATION)
@Inheritance(strategy = InheritanceStrategy.NEW_TABLE)
public class Person extends Agent
{
    private static final Logger log = Logger.getLogger (Person.class.getName ());

    @Persistent
    private String              userKey;

    @Persistent
    private Long                redirectId;

    @Persistent
    private boolean             identified;

    public Person()
    {
    }

    public static Person accessByEmail (PersistenceManager aDatabase, String aEmail)
    {
        return accessByEmail (aDatabase, aEmail, null);
    }

    public static Person accessByEmail (PersistenceManager aDatabase, String aEmail, String aName)
    {
        if (aDatabase == null)
        {
            throw new NullPointerException ("aDatabase");
        }

        aEmail = aEmail.toLowerCase ().trim ();

        Person user = getFirstWhere (aDatabase, Person.class, "email", "String", aEmail);
        if (user == null)
        {
            user = new Person ();
            user.setEmail (aEmail);
            aDatabase.makePersistent (user);
            log.info ("Created new user in database: " + aEmail + ", " + user.getUserKey ());
        }

        if (user.getName () == null && aName != null)
        {
            user.setName (aName);
        }

        user.setDatabase (aDatabase);
        return user;
    }

    private static Person intNormalize (PersistenceManager aDatabase, Person r)
    {
        return r;
    }

    public static Person load (PersistenceManager aDatabase, long aUserId)
    {
        return aDatabase.getObjectById (Person.class, aUserId);
    }

    public static Person locateByUserKey (PersistenceManager aDatabase, String aUserKey)
    {
        return getFirstWhere (aDatabase, Person.class, "userKey", "String", aUserKey);
    }

    /**
     * Generate a new GUID to identify this person
     * 
     * @return
     */
    private String generateKey ()
    {
        return UUID.randomUUID ().toString ();
    }

    public String getBestName ()
    {
        if (StringExtensions.isNotEmpty (getName ()))
        {
            return getName ();
        }
        else
        {
            return getEmail ();
        }
    }

    public Long getRedirectId ()
    {
        return redirectId;
    }

    public String getUserKey ()
    {
        return userKey;
    }

    public boolean isIdentified ()
    {
        return identified;
    }

    public boolean isUnregistered ()
    {
        return !isIdentified ();
    }

    @Override
    public void setEmail (String newEmail)
    {
        if (!newEmail.equals (getEmail ()))
        {
            super.setEmail (newEmail);
            userKey = generateKey ();
        }
    }

    public void setIdentified (boolean identified)
    {
        this.identified = identified;
    }

    public void setRedirectId (Long redirectId)
    {
        this.redirectId = redirectId;
    }
}
